package io.gitee.kotle.android.utils


import com.gsls.gt.GT
import io.gitee.kotle.android.BaseLibraryConfig
import okhttp3.FormBody
import okhttp3.Interceptor
import okhttp3.Response
import okhttp3.internal.readBomAsCharset
import java.util.zip.GZIPInputStream

/**
 * 代码块只有在debug模式下运行
 */
inline fun <RESULT> doOnlyDebug(block: () -> RESULT): RESULT? {
    if (BaseLibraryConfig.isDebug) {
        return block.invoke()
    }
    return null
}

/**
 * 仅在debug环境下，打印错误堆栈
 */
inline fun printStackTrace(block: () -> Throwable?) {
    doOnlyDebug {
        block.invoke()?.printStackTrace()
    }
}

class LogInfo(
    var msg: String?,
    var title: String? = null,
    var tag: Array<String>? = null,
    var stackTraceClass: Boolean = false,
    var stackTraceCode: Boolean = false,
)

/**
 * 仅在debug环境下，打印verbose级别的日志
 * 普通日志
 */
inline fun log(title: String? = null, vararg tag: String, block: () -> String?) {
    doOnlyDebug {
        val msg = block.invoke() ?: "null"
        GT.log(title, msg, *tag)
    }
}

/**
 * 仅在debug环境下，打印verbose级别的日志
 * 错误日志
 */
inline fun logE(title: String? = null, vararg tag: String, block: () -> String?) {
    doOnlyDebug {
        val msg = block.invoke() ?: "null"
        GT.err(title, msg, *tag)
    }
}


/**
 * 仅在debug环境下，打印verbose级别的日志
 * 可以打印json
 */
inline fun logEAll(title: String? = null, vararg tag: String, block: () -> String?) {
    doOnlyDebug {
        val msg = block.invoke() ?: "null"
        GT.errAll(title, msg, *tag)
    }
}

/**
 * 仅在debug环境下，打印verbose级别的日志
 * 可以打印json
 */
inline fun logAll(title: String? = null, vararg tag: String, block: () -> String?) {
    doOnlyDebug {
        val msg = block.invoke() ?: "null"
        GT.logAll(title, msg, *tag)
    }
}


/**
 * 打印Http请求日志
 */
fun httpRequestLog(chain: Interceptor.Chain): Response {
    val request = chain.request()
    val bodyStr = StringBuilder()
    val requestParams = when (val body = request.body) {
        is FormBody -> {
            repeat(body.size) {
                bodyStr.append(body.encodedName(it))
                bodyStr.append(":")
                bodyStr.append(body.encodedValue(it))
                bodyStr.append(",")
            }
            bodyStr.toString()
        }

        else -> {
            bodyStr.append(body.toString())
            bodyStr.append("\n不是FormBody，不支持打印请求参数").toString()
        }
    }
    val requestLog =
        "发送请求：${request.url}\n请求参数：${requestParams}\n请求头:\n${request.headers}"
    GT.logAll("HTTP REQUEST", requestLog)
    val startTime = System.nanoTime()
    val response = chain.proceed(request)
    val endTime = System.nanoTime()
    val oldSource = response.body?.source() ?: return response
    oldSource.request(java.lang.Long.MAX_VALUE)
    val buffer = oldSource.buffer.clone()
    val charset =
        buffer.readBomAsCharset(
            response.body?.contentType()?.charset(Charsets.UTF_8) ?: Charsets.UTF_8
        )
    val responseStr = if (
        response.header("Content-Encoding")?.contains("gzip", true) == true ||
        response.header("Accept-Encoding")?.contains("gzip", true) == true
    ) {
        GZIPInputStream(buffer.inputStream()).bufferedReader(charset).readText()
    } else {
        buffer.inputStream().bufferedReader(charset).readText()
    }
    val responseLog = "{\'响应链接\':\'${response.request.url}\'," +
            "\'响应请求头\':\'${response.headers}\'," +
            "\'响应时间\':\'${(endTime - startTime) / 1e6} ms\'," +
            "\'响应数据\':${responseStr}}"
    GT.logAll("HTTP RESPONSE", responseLog)
    return response
}


